{
 "cells": [
  {
   "cell_type": "markdown",
   "id": "a44d3ce5",
   "metadata": {},
   "source": [
    "# LangChain中的向量数据库"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 3,
   "id": "17b04bc2",
   "metadata": {},
   "outputs": [],
   "source": [
    "# 实例化一个嵌入模型\n",
    "from langchain_community.embeddings import DashScopeEmbeddings"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 4,
   "id": "82ee0c45",
   "metadata": {},
   "outputs": [],
   "source": [
    "embedding_model = DashScopeEmbeddings(\n",
    "    model=\"text-embedding-v4\",\n",
    "    dashscope_api_key=\"sk-da90821cf9174fbeb854011015c67aad\"\n",
    ")"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "b6e50398",
   "metadata": {},
   "source": [
    "### 一、创建数据库"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "56daa03b",
   "metadata": {},
   "outputs": [],
   "source": [
    "# 使用chroma之前要下载对于的包\n",
    "!pip install langchain-chroma"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "950ea91d",
   "metadata": {},
   "outputs": [],
   "source": [
    "# 使用Chroma来存放向量数据\n",
    "from langchain_chroma import Chroma"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "9dd21139",
   "metadata": {},
   "outputs": [],
   "source": [
    "# 实例化一个数据库对象，或者叫做创建数据库连接\n",
    "vector_store = Chroma(\n",
    "    collection_name=\"example_collection\",  # 给向量数据库一个集合\n",
    "    persist_directory=\"./chroma_langchain_db\",  # 数据集路径\n",
    "    embedding_function=embedding_model,  # 指定嵌入模型\n",
    ")"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "c75aa7ad",
   "metadata": {},
   "source": [
    "### 二、操作向量数据库"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "fc0d4249",
   "metadata": {},
   "source": [
    "#### （1）增"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "b67b0ffc",
   "metadata": {},
   "outputs": [],
   "source": [
    "# 手动创建Document对象\n",
    "from langchain_core.documents import Document"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 41,
   "id": "e55c3edb",
   "metadata": {},
   "outputs": [],
   "source": [
    "# 手动创建Document\n",
    "document_1 = Document(\n",
    "    page_content=\"I had chocolate chip pancakes and scrambled eggs for breakfast this morning.\",\n",
    "    metadata={\"source\": \"tweet\"},\n",
    "    id=1,\n",
    ")\n",
    "\n",
    "document_2 = Document(\n",
    "    page_content=\"The weather forecast for tomorrow is cloudy and overcast, with a high of 62 degrees.\",\n",
    "    metadata={\"source\": \"news\"},\n",
    "    id=2,\n",
    ")\n",
    "\n",
    "document_3 = Document(\n",
    "    page_content=\"Building an exciting new project with LangChain - come check it out!\",\n",
    "    metadata={\"source\": \"tweet\"},\n",
    "    id=3,\n",
    ")\n",
    "\n",
    "documents = [\n",
    "    document_1,\n",
    "    document_2,\n",
    "    document_3,\n",
    "]"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "b61e2eaf",
   "metadata": {},
   "outputs": [
    {
     "data": {
      "text/plain": [
       "['1', '2', '3']"
      ]
     },
     "execution_count": 11,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "# add_documents 添加文档到向量数据库里面，它会自动的去做词嵌入\n",
    "vector_store.add_documents(documents)"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "7a91a749",
   "metadata": {},
   "source": [
    "#### （2）删"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "3bdbc938",
   "metadata": {},
   "outputs": [],
   "source": [
    "vector_store.delete(ids='1')  # 给定id去删除"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "a20cb1bd",
   "metadata": {},
   "source": [
    "#### （3）改"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 17,
   "id": "0f13eda3",
   "metadata": {},
   "outputs": [],
   "source": [
    "document = Document(\n",
    "    page_content=\"LangGraph is the best framework for building stateful, agentic applications!\",\n",
    "    metadata={\"source\": \"tweet\"},\n",
    "    id=8,\n",
    ")"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "e9ebb3b3",
   "metadata": {},
   "outputs": [],
   "source": [
    "vector_store.update_document(\n",
    "    document_id=\"2\",  # 对指定id的文档向量去做更新\n",
    "    document=document # 用新的文档去覆盖原来的\n",
    ")"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "c39116e0",
   "metadata": {},
   "source": [
    "#### （4）查"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 33,
   "id": "63048447",
   "metadata": {},
   "outputs": [],
   "source": [
    "# 直接输入文本来查询 similarity_search\n",
    "result = vector_store.similarity_search(\n",
    "    \"LangGraph\",\n",
    "    k=1,\n",
    "    # filter={\"source\": \"tweet\"}  # 默认是相似度搜索\n",
    ")"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 34,
   "id": "44e30d51",
   "metadata": {},
   "outputs": [
    {
     "data": {
      "text/plain": [
       "[Document(id='2', metadata={'source': 'tweet'}, page_content='LangGraph is the best framework for building stateful, agentic applications!')]"
      ]
     },
     "execution_count": 34,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "result"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "46562434",
   "metadata": {},
   "outputs": [],
   "source": [
    "# 把输入文本变成向量来查询 similarity_search_by_vector\n",
    "result = vector_store.similarity_search_by_vector(\n",
    "    embedding_model.embed_query(\"LangGraph\"),   # 第一个参数要是一个向量\n",
    "    k=1  # 返回最相似的K条\n",
    ")"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 36,
   "id": "406f6415",
   "metadata": {},
   "outputs": [
    {
     "data": {
      "text/plain": [
       "[Document(id='2', metadata={'source': 'tweet'}, page_content='LangGraph is the best framework for building stateful, agentic applications!')]"
      ]
     },
     "execution_count": 36,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "result"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 39,
   "id": "77776a28",
   "metadata": {},
   "outputs": [],
   "source": [
    "# 实例化一个检索器来进行查询\n",
    "retriever = vector_store.as_retriever(\n",
    "    search_kwargs={\"k\": 1}\n",
    ")"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 40,
   "id": "99d22bd2",
   "metadata": {},
   "outputs": [
    {
     "data": {
      "text/plain": [
       "[Document(id='2', metadata={'source': 'tweet'}, page_content='LangGraph is the best framework for building stateful, agentic applications!')]"
      ]
     },
     "execution_count": 40,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "retriever.invoke(\"LangGraph\")"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "7cd6e7af",
   "metadata": {},
   "outputs": [],
   "source": []
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": "learn_langchain",
   "language": "python",
   "name": "learn_langchain"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.12.11"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 5
}
